<template>
  <view class="container">
    <!-- 积分卡片 -->
    <view class="points-card">
      <view class="points-header">
        <text class="points-title">我的积分</text>
      </view>
      <view class="points-value">
        <text class="value">{{ userInfo.points }}</text>
      </view>
      <view class="points-actions">
        <view class="action-item" @click="goToPointsRule">
          <text class="action-text">积分规则</text>
        </view>
        <view class="action-item" @click="goToPointsExchange">
          <text class="action-text">积分兑换</text>
        </view>
      </view>
    </view>

    <!-- 积分明细 -->
    <view class="points-detail">
      <view class="detail-header">
        <text class="detail-title">积分明细</text>
      </view>

      <scroll-view scroll-y class="detail-list" @scrolltolower="loadMore" refresher-enabled :refresher-triggered="refreshing"
        @refresherrefresh="onRefresh" :lower-threshold="100">
        <view v-if="pointsRecords.length > 0">
          <view class="detail-item" v-for="(item, index) in pointsRecords" :key="index">
            <view class="item-info">
              <text class="item-title">{{ item.title }}</text>
              <text class="item-time">{{ item.time }}</text>
            </view>
            <text class="item-value" :class="{ increase: item.value > 0 }">{{ item.value > 0 ? '+' : '' }}{{ item.value
              }}</text>
          </view>
        </view>

        <!-- 空状态 -->
        <view v-else class="empty-state">
          <image class="empty-icon" src="/static/icons/empty-points.svg" mode="aspectFit"></image>
          <text class="empty-text">暂无积分记录</text>
        </view>

        <!-- 加载更多 -->
        <view class="loading-more" v-if="loading && pointsRecords.length > 0">
          <text>加载中...</text>
        </view>

        <!-- 没有更多数据 -->
        <view class="no-more" v-if="!hasMore && pointsRecords.length > 0">
          <text>没有更多数据了</text>
        </view>
      </scroll-view>
    </view>
  </view>
</template>

<script setup>
import { ref } from 'vue'
import { onLoad } from '@dcloudio/uni-app'
import { getUserInfo, getPointsRecordPage } from '@/api/user.js'

// 响应式状态
const userInfo = ref({})
const refreshing = ref(false)
const loading = ref(false)
const pointsRecords = ref([])
const page = ref(1)
const pageSize = ref(10)
const hasMore = ref(true)

/**
 * 获取用户信息
 */
const fetchUserInfo = async () => {
  try {
    loading.value = true
    const { data } = await getUserInfo()
    userInfo.value = data
  } catch (error) {
    console.error('获取用户信息失败:', error)
    uni.showToast({
      title: '获取用户信息失败',
      icon: 'none'
    })
  } finally {
    loading.value = false
  }
}

/**
 * 获取积分记录
 */
const loadPointsRecords = async () => {
  loading.value = true
  
  try {
    const params = {
      pageNo: page.value,
      pageSize: pageSize.value
    }
    
    const { data } = await getPointsRecordPage(params)
    
    if (data && data.list) {
      // 转换数据格式以匹配前端显示
      const formattedRecords = data.list.map(record => ({
        title: getRecordTitle(record),
        time: formatTime(record.createTime),
        value: record.type === 1 ? record.points : -record.points
      }))
      
      if (page.value === 1) {
        pointsRecords.value = formattedRecords
      } else {
        pointsRecords.value = [...pointsRecords.value, ...formattedRecords]
      }
      
      // 判断是否还有更多数据
      hasMore.value = data.total > pointsRecords.value.length
    }
  } catch (error) {
    console.error('获取积分记录失败:', error)
    uni.showToast({
      title: '获取积分记录失败',
      icon: 'none'
    })
  } finally {
    loading.value = false
  }
}

/**
 * 根据积分记录生成标题
 */
const getRecordTitle = (record) => {
  const typeText = record.type === 1 ? '获得' : '消费'
  
  switch (record.source) {
    case 'order':
      return record.type === 1 ? '下单奖励' : '订单消费'
    case 'exchange':
      return '积分兑换'
    case 'sign':
      return '签到奖励'
    default:
      return record.description || `积分${typeText}`
  }
}

/**
 * 格式化时间
 */
const formatTime = (timeStr) => {
  if (!timeStr) return ''
  const date = new Date(timeStr)
  const year = date.getFullYear()
  const month = String(date.getMonth() + 1).padStart(2, '0')
  const day = String(date.getDate()).padStart(2, '0')
  const hours = String(date.getHours()).padStart(2, '0')
  const minutes = String(date.getMinutes()).padStart(2, '0')
  return `${year}-${month}-${day} ${hours}:${minutes}`
}

/**
 * 加载更多数据
 */
const loadMore = () => {
  console.log('loadMore', page.value, hasMore.value, loading.value)
  if (!hasMore.value || loading.value) return
  
  page.value++
  loadPointsRecords()
}

/**
 * 初始化数据
 */
const initData = async () => {
  await fetchUserInfo()
  page.value = 1
  await loadPointsRecords()
}

/**
 * 下拉刷新处理
 */
const onRefresh = () => {
  refreshing.value = true
  page.value = 1
  
  // 重新加载数据
  setTimeout(async () => {
    try {
      await fetchUserInfo()
      await loadPointsRecords()
    } catch (error) {
      console.error('刷新失败:', error)
    } finally {
      refreshing.value = false
    }
  }, 1000)
}

/**
 * 跳转到积分规则页面
 */
const goToPointsRule = () => {
  uni.navigateTo({
    url: '/pages/user/points-rule'
  })
}

/**
 * 跳转到积分兑换页面
 */
const goToPointsExchange = () => {
  uni.showToast({
    title: '积分兑换功能暂未开放',
    icon: 'none',
    duration: 2000
  })
}

// 页面加载时初始化数据
onLoad(async () => {
  await initData()
})
</script>

<style lang="scss" scoped>
.container {
  min-height: 100vh;
  background-image: linear-gradient(135deg, #fff8f8 0%, #fff5f7 50%, #fff8fa 100%);
  padding: 30rpx;
}

.points-card {
  background: linear-gradient(135deg, #ff9a9e 0%, #ff6b6b 100%);
  border-radius: 24rpx;
  padding: 40rpx;
  color: #fff;
  margin-bottom: 30rpx;
  box-shadow: 0 8rpx 32rpx rgba(255, 107, 107, 0.2);
  position: relative;
  overflow: hidden;

  &::before {
    content: '';
    position: absolute;
    top: 0;
    left: 0;
    width: 100%;
    height: 100%;
    background: linear-gradient(45deg,
        rgba(255, 255, 255, 0.1) 25%,
        transparent 25%,
        transparent 50%,
        rgba(255, 255, 255, 0.1) 50%,
        rgba(255, 255, 255, 0.1) 75%,
        transparent 75%,
        transparent);
    background-size: 100rpx 100rpx;
    opacity: 0.1;
  }

  .points-header {
    margin-bottom: 30rpx;
    position: relative;

    .points-title {
      font-size: 32rpx;
      font-weight: 600;
      text-shadow: 0 2rpx 4rpx rgba(0, 0, 0, 0.1);
      position: relative;
      display: inline-block;

      &::after {
        content: '';
        position: absolute;
        bottom: -8rpx;
        left: 0;
        width: 40rpx;
        height: 4rpx;
        background: #fff;
        border-radius: 2rpx;
      }
    }
  }

  .points-value {
    text-align: center;
    margin-bottom: 40rpx;

    .value {
      font-size: 88rpx;
      font-weight: 600;
      text-shadow: 0 4rpx 8rpx rgba(0, 0, 0, 0.1);
      background: linear-gradient(to right, #fff, rgba(255, 255, 255, 0.8));
      -webkit-background-clip: text;
      -webkit-text-fill-color: transparent;
      letter-spacing: 2rpx;
    }
  }

  .points-actions {
    display: flex;
    justify-content: space-around;

    .action-item {
      background: rgba(255, 255, 255, 0.15);
      backdrop-filter: blur(10rpx);
      padding: 12rpx 36rpx;
      border-radius: 30rpx;
      border: 1rpx solid rgba(255, 255, 255, 0.2);
      transition: all 0.3s ease;

      &:active {
        transform: scale(0.95);
        background: rgba(255, 255, 255, 0.2);
      }

      .action-text {
        font-size: 26rpx;
        font-weight: 500;
      }
    }
  }
}

.points-detail {
  background: rgba(255, 255, 255, 0.95);
  border-radius: 24rpx;
  padding: 30rpx;
  box-shadow: 0 4rpx 20rpx rgba(0, 0, 0, 0.03);
  backdrop-filter: blur(20rpx);

  .detail-header {
    margin-bottom: 30rpx;

    .detail-title {
      font-size: 32rpx;
      font-weight: 600;
      color: #333;
      position: relative;
      padding-left: 20rpx;

      &::before {
        content: '';
        position: absolute;
        left: 0;
        top: 50%;
        transform: translateY(-50%);
        width: 6rpx;
        height: 28rpx;
        background: linear-gradient(to bottom, #ff9a9e, #ff6b6b);
        border-radius: 6rpx;
      }
    }
  }

  .detail-list {
    max-height: calc(100vh - 500rpx);
  }

  .detail-item {
    display: flex;
    justify-content: space-between;
    align-items: center;
    padding: 24rpx 0;
    position: relative;
    transition: all 0.3s ease;

    &:active {
      background: rgba(0, 0, 0, 0.02);
    }

    &::after {
      content: '';
      position: absolute;
      left: 0;
      right: 0;
      bottom: 0;
      height: 1rpx;
      background: linear-gradient(to right,
          transparent,
          rgba(0, 0, 0, 0.05) 20%,
          rgba(0, 0, 0, 0.05) 80%,
          transparent);
    }

    &:last-child::after {
      display: none;
    }

    .item-info {
      .item-title {
        font-size: 28rpx;
        color: #333;
        margin-bottom: 8rpx;
        display: block;
        font-weight: 500;
      }

      .item-time {
        font-size: 24rpx;
        color: #999;
      }
    }

    .item-value {
      font-size: 32rpx;
      font-weight: 600;
      color: #333;

      &.increase {
        background: linear-gradient(135deg, #ff9a9e, #ff6b6b);
        -webkit-background-clip: text;
        -webkit-text-fill-color: transparent;
      }
    }
  }
}

.empty-state {
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  padding: 80rpx 0;

  .empty-icon {
    width: 240rpx;
    height: 240rpx;
    margin-bottom: 30rpx;
    opacity: 0.8;
  }

  .empty-text {
    font-size: 28rpx;
    color: #999;
    background: linear-gradient(135deg, #999, #666);
    -webkit-background-clip: text;
    -webkit-text-fill-color: transparent;
  }
}

.loading-more,
.no-more {
  text-align: center;
  padding: 30rpx 0;
  font-size: 26rpx;
  color: #999;
  letter-spacing: 2rpx;
}

.no-more {
  position: relative;

  &::before,
  &::after {
    content: '';
    position: absolute;
    top: 50%;
    width: 80rpx;
    height: 2rpx;
    background-color: #eee;
  }

  &::before {
    right: calc(50% + 40rpx);
  }

  &::after {
    left: calc(50% + 40rpx);
  }
}
</style>